package com.taobao.message.service;

import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.stereotype.Component;
import org.springframework.web.socket.TextMessage;
import org.springframework.web.socket.WebSocketSession;
import org.springframework.web.socket.handler.TextWebSocketHandler;

import java.io.IOException;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.*;
import java.util.concurrent.ConcurrentHashMap;

@Component
public class ChatWebSocketHandler extends TextWebSocketHandler {

    // 存储所有在线会话
    private static final Map<WebSocketSession, String> onLineSessions = new ConcurrentHashMap<>();

    private final ObjectMapper objectMapper = new ObjectMapper();

    @Override
    public void afterConnectionEstablished(WebSocketSession session) throws Exception {
        System.out.println("客户端连接：" + session.getId());
    }

    @Override
    protected void handleTextMessage(WebSocketSession session, TextMessage message) throws Exception {
        // 解析收到的消息
        Map<String, Object> payload = objectMapper.readValue(message.getPayload(), Map.class);
        int type = (int) payload.get("type");

        switch (type) {
            case 1: // 登录消息
                String nickname = (String) payload.get("nickname");
                onLineSessions.put(session, nickname);
                updateClientList();
                break;

            case 2: // 群聊消息
                String msg = (String) payload.get("message");
                broadcastMessage(msg, session);
                break;

            case 3: // 私聊消息
                String targetNickname = (String) payload.get("target");
                String privateMsg = (String) payload.get("message");
                sendPrivateMessage(targetNickname, privateMsg, session);
                break;

            default:
                System.out.println("未知消息类型：" + type);
        }
    }

    @Override
    public void afterConnectionClosed(WebSocketSession session, org.springframework.web.socket.CloseStatus status) throws Exception {
        System.out.println("客户端断开：" + session.getId());
        onLineSessions.remove(session);
        updateClientList();
    }

    // 广播群聊消息
    private void broadcastMessage(String msg, WebSocketSession sender) throws IOException {
        String senderNickname = onLineSessions.get(sender);
        LocalDateTime time = LocalDateTime.now();
        DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss EEE a");
        String formattedTime = time.format(formatter);

        String fullMessage = formattedTime + " " + senderNickname + "\n" + msg + "\n";

        for (WebSocketSession session : onLineSessions.keySet()) {
            session.sendMessage(new TextMessage(objectMapper.writeValueAsString(Map.of(
                    "type", 2,
                    "message", fullMessage
            ))));
        }
    }

    // 更新所有客户端的在线用户列表
    private void updateClientList() throws IOException {
        List<String> users = new ArrayList<>(onLineSessions.values());

        for (WebSocketSession session : onLineSessions.keySet()) {
            session.sendMessage(new TextMessage(objectMapper.writeValueAsString(Map.of(
                    "type", 1,
                    "users", users
            ))));
        }
    }

    // 发送私聊消息
    private void sendPrivateMessage(String targetNickname, String msg, WebSocketSession sender) throws IOException {
        String senderNickname = onLineSessions.get(sender);
        LocalDateTime time = LocalDateTime.now();
        DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss EEE a");
        String formattedTime = time.format(formatter);

        String fullMessage = formattedTime + " [" + senderNickname + " 私聊你] \n" + msg + "\n";

        for (Map.Entry<WebSocketSession, String> entry : onLineSessions.entrySet()) {
            if (entry.getValue().equals(targetNickname)) {
                entry.getKey().sendMessage(new TextMessage(objectMapper.writeValueAsString(Map.of(
                        "type", 3,
                        "message", fullMessage
                ))));
                break;
            }
        }
    }
}